package com.mini.service;

import com.mini.conditon.GroupManagerQueryCondition;
import com.mini.config.BusinessException;
import com.mini.constant.GoalStatusEnum;
import com.mini.model.BusinessGroupBase;
import com.mini.repository.BusinessGroupBaseRepository;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.data.domain.Sort;
import org.springframework.data.jpa.domain.Specification;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;
import javax.persistence.criteria.CriteriaBuilder;
import javax.persistence.criteria.CriteriaQuery;
import javax.persistence.criteria.Predicate;
import javax.persistence.criteria.Root;
import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Objects;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 * @author: zhaocg
 * @created: 2020/12/02 11:59
 */
@Slf4j
@Service
public class BusinessGroupBaseService extends BaseService{

    @Autowired
    private BusinessGroupBaseRepository groupBaseRepository;

    /**
     * 分业获取业务组数据
     *
     * @param condition
     * @return
     */
    public Page<BusinessGroupBase> groupPageList(GroupManagerQueryCondition condition){
        Pageable pageable = buildPageRequest(condition.getPageNumber(),condition.getPageSize(),new Sort(Sort.Direction.DESC,"createTime"));
        return groupBaseRepository.findAll(this.getGroupBaseSpecification(condition) ,pageable);
    }

    private Specification<BusinessGroupBase> getGroupBaseSpecification(GroupManagerQueryCondition condition){
        return new Specification<BusinessGroupBase>() {
            @Override
            public Predicate toPredicate(Root<BusinessGroupBase> root, CriteriaQuery<?> criteriaQuery, CriteriaBuilder criteriaBuilder) {
                List<Predicate> predicates = new ArrayList<>();
                if (StringUtils.isNotBlank(condition.getKeyWord())) {
                    Predicate groupName = criteriaBuilder.like(root.get("groupName").as(String.class) , "%"+condition.getKeyWord()+"%");
                    if (isNumeric(condition.getKeyWord())) {
                        Predicate businessGroupId = criteriaBuilder.equal(root.get("id").as(Long.class), condition.getKeyWord());
                        predicates.add(criteriaBuilder.or(businessGroupId , groupName));
                    } else {
                        predicates.add(groupName);
                    }

                }
                if (!CollectionUtils.isEmpty(condition.getIdList())) {
                    CriteriaBuilder.In<Long> in = criteriaBuilder.in(root.get("id"));
                    condition.getIdList().forEach(o->in.value(o));
                    predicates.add(in);
                }
                return criteriaBuilder.and(predicates.toArray(new Predicate[predicates.size()]));
            }
        };
    }

    /**
     * 判断是否为数字
     *
     * @param str
     * @return
     */
    public static boolean isNumeric(String str) {
        // 该正则表达式可以匹配所有的数字 包括负数
        Pattern pattern = Pattern.compile("-?[0-9]+(\\.[0-9]+)?");
        String bigStr;
        try {
            bigStr = new BigDecimal(str).toString();
        } catch (Exception e) {
            return false;//异常 说明包含非数字。
        }

        Matcher isNum = pattern.matcher(bigStr); // matcher是全匹配
        if (!isNum.matches()) {
            return false;
        }
        return true;
    }

    /**
     * 保存业务组基本数据
     *
     * @param groupBase
     * @return
     */
    public BusinessGroupBase save(BusinessGroupBase groupBase){
        Date date = new Date();
        groupBase.setCreateTime(date);
        groupBase.setUpdateTime(date);
        groupBase.setStates(GoalStatusEnum.VALID.getCode());
        return groupBaseRepository.save(groupBase);
    }

    /**
     * 删除业务组
     *
     * @param businessGroupBase
     */
    public void deleted(BusinessGroupBase businessGroupBase){
        if (Objects.isNull(businessGroupBase)) {
            throw new BusinessException("数据不合法");
        }
        groupBaseRepository.delete(businessGroupBase);
    }

    /**
     * 根据ID查找数据
     *
     * @param id
     * @return
     */
    public BusinessGroupBase findById(Long id){
        return groupBaseRepository.findOne(id);
    }

}
